# -*- coding: utf-8 -*-
import matplotlib.pyplot as plt
import gtk
import pygtk
import tempfile

class GeneratorGolda:
    """Podstawowa klasa Generator"""
    def __init__(self):
	
        self.__mSeqs = [] #Msequences
        self.__odczeps= [] #Odczepy
        self.__gold = []  #kod Golda
        self.__startSeq = [] #sekwencja startowa
        self.__gensCount = 0
        self.__regLength = 0
        self.__mSeqsPeriod = [0,0,0]

    def setGensCount(self,x):
        self.__gensCount = x
        
    def getGensCount(self):
        return self.__gensCount 

    def setRegLength(self,x):
        self.__regLength = x;

    def getGensLength(self):
        return self.__regLength

    def setOdczepy(self,genNo, odczep):
        if self.__regLength > 0:
            if self.__regLength == len(odczep):
                try:
                    self.__odczeps[genNo] = odczep
                except IndexError:
                    self.__odczeps.insert(genNo, odczep)
                    
            else:
                print "Unable to add Odczep, different register size"
        else:
            print "register size unspecified"        
        
    def setStartSeq(self, genNo, startSeq):
        if self.__regLength == len(startSeq):
            try:
                self.__startSeq[genNo] = startSeq
            except IndexError:
                self.__startSeq.insert(genNo,startSeq)
        else:
            if self.__regLength == 0:
                print "GeneratorGolda > Set registers lentgh first"
            else:
                print "GeneratorGolda > Length of starting sequence must be equal to registers legth."
   
    def getOdczepy(self, genNo):
        return self.odczeps[genNo]
        #try:
        #     return self.odczeps[genNo]
        #except:
        #    return []   
        
    def getmSeq(self, genNo):
        return self.__mSeqs[genNo] #lalala
    
    def getGold(self):
        return self.__gold

    def getStartSeq(self, genNo):
        return self.__startSeq
    
    def generate(self): #main methods, created mSeq and GOLD
        ##generacja MSequences
        
        if self.__startSeq == []:               
            startSeq = [1]
            for i in range(0, self.__regLength - 1):
                startSeq.append(0)
            for i in range(0, self.__gensCount):
                self.__startSeq.insert(i, startSeq)

        for i in range(0, self.__gensCount):
            self.__mSeqs.insert(i,[])
            register = list(self.__startSeq[i])
            for j in range(0, 2**self.__regLength-1):
                if j > 0:
                #print "reg:" + str(register)
                    if register == self.__startSeq[i]:
                        #print i,j
                        if self.__mSeqsPeriod[i] == 0:
                            self.__mSeqsPeriod[i] = j;
                new_element = -1
                self.__mSeqs[i].append(register[-1])

                for k in range(0, self.__regLength): #calculate new element
                       # print k                        
                    if self.__odczeps[i].getValueAt(k) == True:
                        if new_element == -1:
                            new_element = register[k]
                        else:
                            new_element = new_element ^ register[k]
                
                register[1:] = register[0:len(register)-1]
                
                if new_element == -1:
                    print "GeneratorGolda >> ERROR in generate() new_element = -1!!"
                register[0] = new_element;
       
        
        tempGold = []#obliczanie Golda
        for i in range(0, self.__gensCount): 
            for j in range(0,2**self.__regLength-1):
                if i == 0:
                    tempGold.insert(j,self.__mSeqs[i][j])
                else:    
                    tempGold[j] = tempGold[j] ^ self.__mSeqs[i][j]

        self.__gold = tempGold                          

    def getRealMSeq(self, _genNo):
        out = []
        for i in range(0, len(self.__mSeqs[_genNo])):
            if i > 0 and self.__mSeqsPeriod[_genNo] < i+1 and self.__mSeqsPeriod[_genNo] > 0:
                return out
            out.append(self.__mSeqs[_genNo][i])
        return out
                               
    def printOutput(self, isGold):
        output = ""
        for i in range(0, self.__gensCount):
            output += u"Ciąg pseudolosowy " + str(i+1) +" : \t" + str(self.getRealMSeq(i))
            if len(self.getRealMSeq(i)) != len(self.__mSeqs[i]):
                output += " (nie jest ciągiem maksymalnym)"
            output += "\n"
        if isGold:
		output += "Ciąg Golda :\t\t" + str(self.getGold()) + "\n"
        output += "Autokorelacja :\t\t" + str(correlation(self.getGold(),self.getGold()))   
        return output
    
    def printOutput2(self, a, b):
        output = ""
        output += "Ciąg pseudolosowy %s" % a + " : \t" + str(self.getRealMSeq(0))
        if len(self.getRealMSeq(0)) != len(self.__mSeqs[0]):
            output += " (nie jest ciągiem maksymalnym)"
        output += "\n"
        
        output += "Ciąg pseudolosowy %s" % b + " : \t" + str(self.getRealMSeq(1))
        if len(self.getRealMSeq(1)) != len(self.__mSeqs[1]):
            output += " (nie jest ciągiem maksymalnym)"
        output += "\n"
 
        output += "Korelacja skrośna :\t\t" + str(correlation(self.getmSeq(0),self.getmSeq(1)))   
        return output


class MSequence:
    """Klasa do przechowujaca ciagi maksymalne"""
    def _init_(self):
        self.__seq = []
    def __init__(self,seq):
        self.__seq = seq

    def getSeq(self):
        return self.__seq

    def setSeq(seq):
        self.__seq = seq

class Gold:
    def _init_(self):
        self.__seq = []
    def __init__(self,seq):
        self.__seq = seq

    def getSeq(self):
        return self.__seq

    def setSeq(seq):
        self.__seq = seq


    def setValueAt(self,index, value):
        try:
            self.__seq[index] = value
        except:
            print "Error Gold > setValueAt -> no such an index"
    def getAutocorrelation(self):
        return [1,2,3,4,5]
        ##dorobic


class Odczep:
    def __init__(self):
        self.__schema = []

    def __len__(self):
        return len(self.__schema)
    
    def setOdczep(self,_odczeps):
        self.__schema = _odczeps

    def getOdczep(self):
        try:
             return self.__schema
        except:
            return []

    def setValueAt(_no, _value):
        self.__schema[_no] = _value

    def getValueAt(self, _no):
        try:
            return self.__schema[_no]
        except:
            return -1


def correlation(seq1, seq2):
    if (len(seq1) != len(seq2)):
        print "Funtion Correlation -> Sequences are not equal!"
    else:
        sum=0
        result = []
        for i in range(0, len(seq1)):
            iterator=0
            for j in range(i, len(seq1)):
                if seq1[iterator] == seq2[j]:
                    sum+=1
                else:
                    sum-=1
                iterator+=1
            
            for j in range(0, i):
                if(seq1[iterator]==seq2[j]):
                    sum+=1;
                else:
                    sum-=1
                iterator+=1
            
            result.insert(i,sum)
            sum=0
        return result
    
def createGraph(_seq, _title):
    """ Args: _seq-Sequence to draw, _title-Title of Graph, _filename-Name for PNG file (no extension should be provided"""

    plt.plot(_seq, 'rs--')
    plt.ylabel(u'Wartości korelacji')
    plt.xlabel(u'Przesunięcie')
    plt.grid(True)
    plt.axis([0,len(_seq), min(_seq)-1, len(_seq)+1])
    plt.title(_title)
    #plt.setp(lines, color='r', linewidth=2.0)
    
    f = tempfile.mktemp()
    plt.savefig(f, dpi=80, format='png')
    plt.close()
    return f
    
def autoCorrelationValues(length):
    """Zwraca dopuszczalne , 3 wartosci korelacji skrosnej dla ciagow Golda o podanej dlugosci"""
    N = (2**length) - 1
    if length % 2 == 0:
        t= 2**((length+2)/2) + 1
    else:   
        t= 2**((length+1)/2) + 1

    v1 = -1
    v2 = -t
    v3 = t-2
    return v1,v2,v3
   
if __name__ == "__main__":
    print "Test Valid"
             










    


